#ifndef UTILS_TIMER_H
#define UTILS_TIMER_H

#include <chrono>
#include <string>
#include <functional>
#include <thread>
#include <ctime>


enum data_format{
    FMT_YYhMMhDD=0,     // YYYY-MM-DD
    FMT_YY_MM_DD,       // YYYY_MM_DD
    FMT_YYsMMsDD,       // YYYY/MM/DD
    FMT_YYMMDD,         // YYYYMMDD
    FMT_DATA_EMPTY
};

enum time_format{
    FMT_HHdMMdSS=0,     // HH:MM:SS
    FMT_HHhMMhSS,       // HH-MM-SS
    FMT_HH_MM_SS,       // HH_MM_SS
    FMT_HHMMSS,         // HHMMSS
    FMT_TIME_EMPTY
};

enum data_time_format{
    FMT_YYhMMhDDeHHdMMdSS=0,// YYYY-MM-DD HH:MM:SS
    FMT_YYhMMhDD_HHdMMdSS,  // YYYY-MM-DD_HH:MM:SS
    FMT_YYMMDD_HHMMSS,      // YYYYMMDD_HHMMSS
    FMT_YYMMDDHHMMSS,       // YYYYMMDDHHMMSS
    FMT_EMPTY    
};

class Timer
{
public:
    // ================ 时间获取功能 ================

    /*
        获取当前时间字符串（格式：HH:MM:SS）
        type:
            0=HH:MM:SS
            1=HH-MM-SS
            2=HH_MM_SS
            3=HHMMSS
    */
    static std::string getCurrentTime(time_format type = FMT_HHdMMdSS)
    {
        auto now = std::chrono::system_clock::now();
        std::time_t currentTime = std::chrono::system_clock::to_time_t(now);
        char buffer[9];
        switch (type)
        {
        case FMT_HHdMMdSS:
            std::strftime(buffer, sizeof(buffer), "%H:%M:%S", std::localtime(&currentTime));
            break;
        case FMT_HHhMMhSS:
            std::strftime(buffer, sizeof(buffer), "%H-%M-%S", std::localtime(&currentTime));
            break;
        case FMT_HH_MM_SS:
            std::strftime(buffer, sizeof(buffer), "%H_%M_%S", std::localtime(&currentTime));
            break;
        case FMT_HHMMSS:
            std::strftime(buffer, sizeof(buffer), "%H%M%S", std::localtime(&currentTime));
            break;
        }
        return std::string(buffer);
    }

    /*
        获取当前日期字符串（格式：YYYY-MM-DD）
        type:
            0=YYYY-MM-DD
            1=YYYY_MM_DD
            2=YYYY/MM/DD
            3=YYYYMMDD
    */
    static std::string getCurrentDate(data_format type = FMT_YYhMMhDD)
    {
        auto now = std::chrono::system_clock::now();
        std::time_t currentTime = std::chrono::system_clock::to_time_t(now);
        char buffer[11];
        switch (type)
        {
        case FMT_YYhMMhDD:
            std::strftime(buffer, sizeof(buffer), "%Y-%m-%d", std::localtime(&currentTime));
            break;
        case FMT_YY_MM_DD:
            std::strftime(buffer, sizeof(buffer), "%Y_%m_%d", std::localtime(&currentTime));
            break;
        case FMT_YYsMMsDD:
            std::strftime(buffer, sizeof(buffer), "%Y/%m/%d", std::localtime(&currentTime));
            break;
        case FMT_YYMMDD:
            break;
        }

        return std::string(buffer);
    }

    // 获取当前日期时间字符串（格式：YYYY-MM-DD HH:MM:SS）
    /*
        获取当前日期时间字符串（格式：YYYY-MM-DD）
        type:
            0=YYYY-MM-DD HH:MM:SS
            1=YYYY-MM-DD_HH:MM:SS
            2=YYYYMMDD_HHMMSS
            3=YYYYMMDDHHMMSS
    */
    static std::string getCurrentDateTime(data_time_format type = FMT_YYhMMhDDeHHdMMdSS)
    {
        auto now = std::chrono::system_clock::now();
        std::time_t currentTime = std::chrono::system_clock::to_time_t(now);
        char buffer[20];
        switch (type)
        {
        case FMT_YYhMMhDDeHHdMMdSS:
            std::strftime(buffer, sizeof(buffer), "%Y-%m-%d %H:%M:%S", std::localtime(&currentTime));
            break;
        case FMT_YYhMMhDD_HHdMMdSS:
            std::strftime(buffer, sizeof(buffer), "%Y-%m-%d_%H:%M:%S", std::localtime(&currentTime));
            break;
        case FMT_YYMMDD_HHMMSS:
            std::strftime(buffer, sizeof(buffer), "%Y%m%d_%H%M%S", std::localtime(&currentTime));
            break;
        case FMT_YYMMDDHHMMSS:
            std::strftime(buffer, sizeof(buffer), "%Y%m%d%H%M%S", std::localtime(&currentTime));
            break;
        }
        
        return std::string(buffer);
    }

    // ================ 计时器功能 ================

    // 启动计时器
    void tmStart()
    {
        startTime = std::chrono::high_resolution_clock::now();
        running = true;
    }

    // 停止计时器并返回毫秒数
    long long tmStop()
    {
        if (!running)
            return 0;
        endTime = std::chrono::high_resolution_clock::now();
        running = false;
        return std::chrono::duration_cast<std::chrono::milliseconds>(endTime - startTime).count();
    }

    // 获取当前计时值（毫秒），不停止计时器
    long long tmElapsed() const
    {
        if (!running)
            return 0;
        auto now = std::chrono::high_resolution_clock::now();
        return std::chrono::duration_cast<std::chrono::milliseconds>(now - startTime).count();
    }

    // 重置计时器
    void tmReset()
    {
        running = false;
    }

    // ================ 非阻塞延时功能 ================



    // // 非阻塞延时（带取消功能）
    // class DelayHandle
    // {
    // public:
    //     DelayHandle(int _milliseconds, std::function<void()> _callback)
    //         : active(true), callback(_callback)
    //     {
    //         thread = std::thread([this, _milliseconds]() {
    //             std::this_thread::sleep_for(std::chrono::milliseconds(_milliseconds));
    //             if (active && _callback)
    //                 callback();
    //         });
    //         thread.detach();
    //     }

    //     ~DelayHandle()
    //     {
    //         cancel();
    //     }

    //     void cancel()
    //     {
    //         active = false;
    //     }

    // private:
    //     std::atomic<bool> active;
    //     std::function<void()> callback;
    //     std::thread thread;
    // };

    // // 创建可取消的延时任务
    // static DelayHandle *createCancellableDelay(int _milliseconds, std::function<void()> _callback)
    // {
    //     return new DelayHandle(_milliseconds, _callback);
    // }

private:
    std::chrono::time_point<std::chrono::high_resolution_clock> startTime;
    std::chrono::time_point<std::chrono::high_resolution_clock> endTime;
    bool running = false;
};

#endif // UTILS_TIMER_H
